﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Antlr.Runtime;

namespace XYZCompiler
{
    class FlowController
    {
        public object CurrentStageResult
        {
            get{return _currentStageResult;}
        }
        private object _currentStageResult = null;

        private readonly CompilePartFactory _factory  = new CompilePartFactory();

        public enum CompileState
        {
            ERROR,
            READY,
            LEXER_COMPLETED,
            SYNTACTIC_COMPLETED,
            SEMANTIC_COMPELETED,
        }
        public enum ErrorType
        {
            WARNING,
            ERROR
        }

        public delegate void ErrorHandler(string s, int c, int r);
        public event ErrorHandler Error;

        public delegate void CompileStateChangedHandler(CompileState s);
        public event CompileStateChangedHandler CompileStateChanged;


        public CompileState State
        {
            get { return _state; }
            set 
            {
                _state = value;
                if(CompileStateChanged!=null)
                    CompileStateChanged(_state);

            }
        }
        private CompileState _state  = CompileState.READY;

        public string Source
        {
            get { return _source; }
            set
            {
                if (_state != CompileState.READY)
                    throw new System.Exception("Can't change source when compiling");
                _source = value;
                _currentStageResult = value;
            }
        }
        private string _source;




        public void PartErrorHandler(string s,int c,int r)
        {
            if (Error != null)
                Error(s, c, r);
        }

        public CompileState NextStaget()
        {
            CompilePartBase part = _factory[State];
            part.PartError += PartErrorHandler;
            var result =part.Excute(_currentStageResult);
           // var cts = result.CurrentStageResult as CommonTokenStream;
            part.PartError -= PartErrorHandler;
            _currentStageResult = result.CurrentStageResult;
            State = result.State;
            return State;
        }

        public void Reset()
        {
            _currentStageResult = null;
            State = CompileState.READY;
        }
        

    }
}
